package arithmetic.LeetCode;

import java.util.Arrays;
import java.util.Map;
import java.util.Stack;

import org.junit.jupiter.api.Test;

/**
 * 2. 接雨水
 * 给定 n 个非负整数表示每个宽度为 1 的柱子的高度图，计算按此排列的柱子，下雨之后能接多少雨水。
 * <p>
 * 输入：height = [0,1,0,2,1,0,1,3,2,1,2,1]
 * 输出：6
 * 解释：上面是由数组 [0,1,0,2,1,0,1,3,2,1,2,1] 表示的高度图，在这种情况下，可以接 6 个单位的雨水（蓝色部分表示雨水）。
 * <p>
 * 链接：https://leetcode.cn/problems/trapping-rain-water
 *
 * @author jiangfeng on 2023/4/15
 */
public class TrapRainWater {

    @Test
    public void test(){
        System.out.println(trap(new int[]{0,1,0,2,1,0,1,3,2,1,2,1}));
        System.out.println(trap(new int[]{4,2,0,3,2,5}));
    }


    public int trap(int[] height) {
        //用单调栈,分别计算左边的最大值和右边的极大值.
        int[] left = new int[height.length];
        int[] right = new int[height.length];
        // 算左前缀最值
        left[0]=0;
        for(int i =1;i<height.length;i++){
            left[i] = Math.max(left[i-1],height[i-1]);
        }
        right[height.length-1]=0;
        for(int i =height.length-2;i>=0;i--){
            right[i] = Math.max(right[i+1],height[i+1]);
        }
        System.out.println(Arrays.toString(height));
        System.out.println(Arrays.toString(left));
        System.out.println(Arrays.toString(right));
        int result = 0;
        for(int i =0;i<height.length;i++){
            result+= Math.max(0,Math.min(left[i],right[i])-height[i]);
            int a = Math.max(0,Math.min(left[i],right[i])-height[i]);
            System.out.print(a+", ");
        }
        System.out.println();
        return result;
    }

    public int trap1(int[] height) {
        //用单调栈,分别计算左边的最大值和右边的极大值.
        int[] left = new int[height.length];
        int[] right = new int[height.length];
        left[0] = 0;
        Stack<Integer> st = new Stack();
        //1,2
        int i = 0;
        while (i < height.length || !st.empty()) {
            if (st.empty() || (i < height.length && height[st.peek()] >= height[i])) {
                st.push(i);
                i++;
                continue;
            }
            Integer big = st.pop();
            left[big] = i==height.length?-1:height[i];
            right[big] = st.empty()?-1:st.peek();
        }
        System.out.println(Arrays.toString(left));
        System.out.println(Arrays.toString(right));
        return 0;
    }
}
